package com.leps.nq.sys.service.impl;

import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.leps.nq.common.util.SecurityUtil;
import com.leps.nq.sys.entity.SysMenu;
import com.leps.nq.sys.mapper.SysMenuMapper;
import com.leps.nq.sys.service.ISysMenuService;
import com.leps.nq.sys.vo.CreateMenuVo;
import com.leps.nq.sys.vo.MenuInfoVo;
import org.springframework.stereotype.Service;

import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * <p>
 * 菜单权限表 服务实现类
 * </p>
 *
 * @author hex
 * @since 2022-05-20
 */
@Service
public class SysMenuServiceImpl extends ServiceImpl<SysMenuMapper, SysMenu> implements ISysMenuService {

    public List<MenuInfoVo> treeify(List<SysMenu> source) {
        // map to MenuInfoVo List and group by parentId
        Map<Long, List<MenuInfoVo>> grouped =
                source.stream()
                        .map(m -> BeanUtil.toBean(m, MenuInfoVo.class))
                        .collect(Collectors.groupingBy(MenuInfoVo::getParentId));
        // root tree nodes
        List<MenuInfoVo> vos = grouped.get(0L);
        // fill children
        fillChildren(vos, grouped);
        return vos;
    }

    private void fillChildren(List<MenuInfoVo> vos, Map<Long, List<MenuInfoVo>> grouped) {
        vos.forEach(vo -> {
            List<MenuInfoVo> children = grouped.get(vo.getMenuId());
            if (children == null) return;
            vo.setChildren(children);
            fillChildren(children, grouped);
        });
    }

    @Override
    public List<MenuInfoVo> selectMenusAsTree() {
        return this.treeify(this.selectMenusAsList());
    }

    @Override
    public List<SysMenu> selectMenusAsList() {
        return this.getBaseMapper().selectMenuList(new SysMenu());
    }

    @Override
    public List<SysMenu> selectChildrenByParentId(Long parentId) {
        return new LambdaQueryChainWrapper<SysMenu>(this.getBaseMapper())
                .eq(SysMenu::getParentId, parentId)
                .list();
    }

    @Override
    public boolean createMenu(CreateMenuVo createMenuVo) {
        SysMenu sysMenu = BeanUtil.toBean(createMenuVo, SysMenu.class);
        sysMenu.setCreateBy(SecurityUtil.getUserName());
        if(sysMenu.getParentId() == null) {
            sysMenu.setParentId(0L);
        }
        int rows = this.getBaseMapper().insertMenu(sysMenu);
        return rows > 0;
    }

    @Override
    public boolean updateMenu(SysMenu sysMenu) {
        sysMenu.setUpdateBy(SecurityUtil.getUserName());
        int rows = this.getBaseMapper().updateMenu(sysMenu);
        return rows > 0;
    }

    @Override
    public boolean changeVisible(Long menuId, String visible) {
        SysMenu sysMenu = new SysMenu();
        sysMenu.setMenuId(menuId);
        sysMenu.setVisible(visible);
        sysMenu.setUpdateBy(SecurityUtil.getUserName());
        int rows = this.getBaseMapper().updateMenu(sysMenu);
        return rows > 0;
    }

    @Override
    public boolean changeStatus(Long menuId, String status) {
        SysMenu sysMenu = new SysMenu();
        sysMenu.setMenuId(menuId);
        sysMenu.setStatus(status);
        sysMenu.setUpdateBy(SecurityUtil.getUserName());
        int rows = this.getBaseMapper().updateMenu(sysMenu);
        return rows > 0;
    }

    @Override
    public boolean removeMenus(Long[] menuIds) {
        int rows = this.getBaseMapper().deleteBatchIds(Arrays.asList(menuIds));
        return rows > 0;
    }

    @Override
    public List<Long> selectDeepChidrenByParentId(Long parentId) {
        return this.getBaseMapper().selectDeepChidrenByParentId(parentId);
    }


}
